namespace CRM_Perf_BenchMark
{
    using System;
    using System.Collections.Generic;
    using Microsoft.VisualStudio.TestTools.WebTesting;
    using System.Net;
    using System.Text;
    using System.Xml;
    
    /// <summary>
    /// 1. Start at Sales homepage
    /// 2. Select Opportunities
    /// 3. Select "Open Opportunities" view
    /// 4. Enter a string and click "Find" to search for an Opportunity
    /// 5. Open an opportunity by double clicking an opportunity
    /// 6. Click Actions and Delete the Opportunity
    /// </summary>
    
    public class DeleteOpportunity : CrmWebTest
    {
        public void DeleteOpportunity_PreWebTest(object sender, PreWebTestEventArgs e)
        {
			EntityRequest er = new EntityRequest();
			er.Type = EntityNames.Users;
			er.ReturnAs = EntityNames.Users;
			er.ParentID = EntityManager.Instance.OrgId;

			System.Collections.Hashtable Props = new System.Collections.Hashtable();

            if (e.WebTest.Context.ContainsKey("UserRole"))
            {
                Props.Add("role", e.WebTest.Context["UserRole"]);
            }
            
			EntityRequest OpportunityEr = new EntityRequest();
			OpportunityEr.Type = EntityNames.Opportunities;
			OpportunityEr.ParentID = Guid.NewGuid();
			OpportunityEr.ReturnAs = EntityNames.Opportunities;

            System.Collections.Hashtable opportunityProps = new System.Collections.Hashtable();
            opportunityProps.Add("name", "deletable");
            OpportunityEr.Props = opportunityProps;

			Props.Add(EntityNames.Opportunities, new EntityRequest[] { OpportunityEr });

			er.Props = Props;

			System.Collections.Hashtable Entities = EntityManager.Instance.GetEntities(er);

			user = (CRMEntity)Entities[EntityNames.Users];
			opportunity = (CRMEntity)Entities[EntityNames.Opportunities];
            crmServer = user["CrmServer"];
            tokenKey = EntityManager.Instance.ReadTokenKey(user["organizationid"]);
            
            e.WebTest.UserName = user["domainName"];
            e.WebTest.Password = user["userpassword"];
        }

        public void DeleteOpportunity_PostWebTest(object sender, PostWebTestEventArgs e)
        {
            // Don't free the entity till end of the test run as it is already deleted.
            EntityManager.Instance.DeleteEntity(opportunity);
            EntityManager.Instance.FreeEntity(user);
        }

        public DeleteOpportunity()
        {
            WebRequest.RegisterPrefix("crm", new crmRequestFactory());
            string random = Utils.GetRandomString(2, 2);
            gridXml = GridXmlHelper.OpportunityPageView(-1, openOpportunitiesView, null);
            gridXml2 = GridXmlHelper.OpportunitySearchView(-1, searchOpportunitiesView, random, null);
            gridRefreshXml = GridXmlHelper.OpportunityPageSearchViewRefresh(-1, searchOpportunitiesView, random, null);

            this.Proxy = null;            
            PreWebTest += new EventHandler<PreWebTestEventArgs>(DeleteOpportunity_PreWebTest);
            PostWebTest += new EventHandler<PostWebTestEventArgs>(DeleteOpportunity_PostWebTest);
        }

        public override IEnumerator<WebTestRequest> GetRequestEnumerator()
        {
            AppGridWebService.AppGridWebService ag;
            WebTestRequest wtr;

			this.BeginTransaction("NavOpportunityHomepage");

            // Get the home page
            _root_homepage_aspx hp = new _root_homepage_aspx(user);
            hp.etc = 3;
            yield return (hp);

			this.EndTransaction("NavOpportunityHomepage");

            if (ConfigSettings.Default.alltasks == true)
            {
                this.BeginTransaction("NavOpenOpportunities");

                // Open All Opportunities.
                ag = new AppGridWebService.AppGridWebService();
                wtr = null;

                try { ag.Reset(gridXml, gridId); }
                catch (crmException x)
                {
                    wtr = (CrmRequest)x.wtr;
                    wtr.Url = Utils.ReplaceServerName(wtr.Url, user);

                    string urlPath = wtr.Url.Remove(0, crmServer.Length);
                    urlPath = urlPath.Remove(0, user["organizationName"].Length + 1);

                    rpcInfo = Utils.GenerateWRPCToken(urlPath, user, tokenKey);

                    headerItem = new WebTestRequestHeader();
                    headerItem.Name = "crmwrpctokentimestamp";
                    headerItem.Value = rpcInfo.timeStamp.ToString();
                    wtr.Headers.Add(headerItem);
                    headerItem = new WebTestRequestHeader();
                    headerItem.Name = "crmwrpctoken";
                    headerItem.Value = rpcInfo.token;
                    wtr.Headers.Add(headerItem);
                    wtr.Method = "Post";
                }
                yield return (wtr);

                this.EndTransaction("NavOpenOpportunities");
            }
            
            this.BeginTransaction("SearchOpportunities");

            ag = new AppGridWebService.AppGridWebService();
            wtr = null;

            try { ag.Reset(gridXml2, gridId); }
            catch (crmException x)
            {
                wtr = (CrmRequest)x.wtr;
                wtr.Url = Utils.ReplaceServerName(wtr.Url, user);

                string urlPath = wtr.Url.Remove(0, crmServer.Length);
                urlPath = urlPath.Remove(0, user["organizationName"].Length + 1);

                rpcInfo = Utils.GenerateWRPCToken(urlPath, user, tokenKey);

                headerItem = new WebTestRequestHeader();
                headerItem.Name = "crmwrpctokentimestamp";
                headerItem.Value = rpcInfo.timeStamp.ToString();
                wtr.Headers.Add(headerItem);
                headerItem = new WebTestRequestHeader();
                headerItem.Name = "crmwrpctoken";
                headerItem.Value = rpcInfo.token;
                wtr.Headers.Add(headerItem);
                wtr.Method = "Post";
            }
            yield return (wtr);

            this.EndTransaction("SearchOpportunities");

            this.BeginTransaction("OpenOpportunity");

            // simulate double clicking of Opportunity
            sfa_opps_edit_aspx dp = new sfa_opps_edit_aspx(user);
            dp.id = opportunity["opportunityid"];
            yield return (dp);

            referer = dp.lastResponse.ResponseUri.AbsoluteUri;

            _forms_FormScript_js_aspx f = new _forms_FormScript_js_aspx(user);
            f.etc = 3;
            f.FormType = "main";
            f.FormName = "crmForm";
            headerItem = new WebTestRequestHeader("referer", referer);
            f.Headers.Add(headerItem);
            yield return (f);

			this.EndTransaction("OpenOpportunity");

			this.BeginTransaction("DeleteOpportunity");

            _grid_cmds_dlg_delete_aspx delPage = new _grid_cmds_dlg_delete_aspx(user);
            delPage.iObjType = 3;
            delPage.iTotal = 1;
            delPage.sIds = opportunity["opportunityid"];            
            yield return (delPage);

            _grid_cmds_dlg_delete_aspx delPage2 = new _grid_cmds_dlg_delete_aspx(user);

            rpcInfo = Utils.GenerateWRPCToken(_grid_cmds_dlg_delete_aspx.url, user, tokenKey);
            headerItem = new WebTestRequestHeader();
            headerItem.Name = "CRMWRPCTokenTimeStamp";
            headerItem.Value = rpcInfo.timeStamp.ToString();
            delPage2.Headers.Add(headerItem);
            headerItem = new WebTestRequestHeader();
            headerItem.Name = "CRMWRPCToken";
            headerItem.Value = rpcInfo.token;
            delPage2.Headers.Add(headerItem);
            delPage2.Method = "Post"; 

            delPage2.iObjType = 3;
            delPage2.iTotal = 1;
            delPage2.iIndex = 0;
            delPage2.sSubTypes = null;
            delPage2.sSrcQueueId = null;
            delPage2.sParentId = null;
            delPage2.sCalendarId = null;
            delPage2.iId = opportunity["opportunityid"];

            StringHttpBody httpBody = new StringHttpBody();
            httpBody.BodyString = "<node />";
            httpBody.ContentType = "text/xml";
            delPage2.Body = httpBody;

            yield return (delPage2);

            AppGridWebService.AppGridWebService agws = new AppGridWebService.AppGridWebService();
            WebTestRequest wtrRefresh = null;
            try { agws.Refresh(gridRefreshXml); }
            catch (crmException x)
            {
                wtrRefresh = x.wtr;
                wtrRefresh.Url = Utils.ReplaceServerName(wtrRefresh.Url, user);

                string urlPath = wtrRefresh.Url.Remove(0, crmServer.Length);
                urlPath = urlPath.Remove(0, user["organizationName"].Length + 1);

                rpcInfo = Utils.GenerateWRPCToken(urlPath, user, tokenKey);

                headerItem = new WebTestRequestHeader();
                headerItem.Name = "crmwrpctokentimestamp";
                headerItem.Value = rpcInfo.timeStamp.ToString();
                wtrRefresh.Headers.Add(headerItem);
                headerItem = new WebTestRequestHeader();
                headerItem.Name = "crmwrpctoken";
                headerItem.Value = rpcInfo.token;
                wtrRefresh.Headers.Add(headerItem);
                wtrRefresh.Method = "Post";
            }
            yield return (wtrRefresh);

            this.EndTransaction("DeleteOpportunity");
        }

        private string gridXml;
        private string gridXml2;
        private string gridRefreshXml;
        private static string gridId = "crmGrid";

        private static string searchOpportunitiesView = "3F6D889E-6549-4025-9CE0-4C4103EFB6A3";
        private static string openOpportunitiesView = "00000000-0000-0000-00AA-000010003001";

        private CRMEntity user;
        private CRMEntity opportunity;
        private string crmServer;
        private string tokenKey;

        private WRPCInfo rpcInfo;
        private WebTestRequestHeader headerItem;
        private string referer;
    }
}